package com.jdd.fintech.morse.test;

import com.google.common.collect.Maps;
import com.jd.fastjson.JSONObject;
import com.jdd.fintech.morse.plugin.MoresOpenApiDecryptsFilter;
import com.jdd.fintech.morse.plugin.constans.OpenApiConstans;
import com.jdd.fintech.morse.plugin.enums.BooleanEnum;
import com.jdd.fintech.morse.plugin.enums.CustomVersionEnum;
import com.jdd.fintech.morse.plugin.enums.EncrAndDecrAlgorithmTypeEnum;
import com.jdd.fintech.morse.plugin.enums.RequestDateDirectionEnum;
import com.jddglobal.engine.boot.ImmutableChain;
import com.jddglobal.filter.Filter;
import com.jddglobal.filter.data.Context;
import com.jddglobal.filter.data.Resource;
import com.jddglobal.util.bean.BeanMapper;
import org.junit.Test;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import java.util.ArrayList;
import java.util.List;
import java.util.TreeSet;

/**
 * @description：测试加解密测试类
 * @className：AppTest
 * @author：ext.fengcheng
 * @date：2023/12/27 14:52
 */
public class MorseOpenApiPluginTest extends AppTest{

    private static final Logger log = LoggerFactory.getLogger(MorseOpenApiPluginTest.class);

    /**
     * filter chain config.
     * @return
     */
    public ImmutableChain.Invoker invoker () {
        TreeSet<ImmutableChain.FilterChainSetting> filterSet = new TreeSet<>();

//        filterSet.add(chainSetting(MorseOpenApiEncryptsFilter.class, 1, bulidMorseEncryptPlugValue()));
        filterSet.add(chainSetting(MoresOpenApiDecryptsFilter.class, 2, bulidMorseDecryptPlugValue()));

        return ImmutableChain.Invoker.compile("move_chain", filterSet);
    }

    /**
     * filter info construct.
     * @param cls
     * @param order
     * @param <T>
     * @return
     */
    static <T extends Filter> ImmutableChain.FilterChainSetting chainSetting(Class<T> cls, int order, List<Filter.ConfigurationValue> filterValues) {
        ImmutableChain.FilterSetting filter = new ImmutableChain.FilterSetting();
        filter.setId((long)order);
        filter.setFilterClass(cls.getName());
        ImmutableChain.FilterChainSetting setting = BeanMapper.map(filter, ImmutableChain.FilterChainSetting.class);
        setting.setOrder(order);
        setting.setCls(cls);
        setting.setConfigValue(filterValues);
        setting.setFilterSetting(filter);
        return setting;
    }

    /**
     * 构建morse加密插件值
     * @return
     */
    private List<Filter.ConfigurationValue> bulidMorseEncryptPlugValue() {
        Filter.ConfigurationValue configurationValue = new Filter.ConfigurationValue();
        JSONObject jsonObject = new JSONObject();
        jsonObject.put("encyAndDecyFlag", BooleanEnum.YES);                         //是否加解密
        jsonObject.put("encyAndDecyType", EncrAndDecrAlgorithmTypeEnum.AES);                  //加解密类型
        jsonObject.put("publicSecurity", "1234561234561234");                       //加密密钥
        jsonObject.put("privateSecurity", "1234561234561234");                      //解密密钥
        jsonObject.put("keySize", "16");                                            //密钥长度
        jsonObject.put("salt", "789789");                                           //盐值
        jsonObject.put("isComplete", BooleanEnum.NO);                               //是否完整加解密
        jsonObject.put("encryptMode", OpenApiConstans.ENCRYPT_MODE_CBC);            //加密模式
        jsonObject.put("customVersion", CustomVersionEnum.G);                       //定制化版本枚举
        jsonObject.put("requestDateDirection", RequestDateDirectionEnum.REQUEST);  //加解密入口
        jsonObject.put("isFile", BooleanEnum.NO);                                  //是否是文件
        jsonObject.put("encyAndDecyFieldKey", "infoContent");                                  //是否是文件
        jsonObject.put("dataContentKey", "infoContent");                                  //是否是文件
        jsonObject.put("signKey", "infoSign");                                  //是否是文件
        configurationValue.setSettingValue(jsonObject.toJSONString());
        List<Filter.ConfigurationValue> list = new ArrayList<Filter.ConfigurationValue>();
        list.add(configurationValue);
        return list;
    }
    /**
     * 构建morse解密插件值
     * @return
     */
    private List<Filter.ConfigurationValue> bulidMorseDecryptPlugValue() {
        Filter.ConfigurationValue configurationValue = new Filter.ConfigurationValue();
        JSONObject jsonObject = new JSONObject();
        jsonObject.put("encyAndDecyFlag", BooleanEnum.YES);                         //是否加解密
        jsonObject.put("encyAndDecyType", EncrAndDecrAlgorithmTypeEnum.AES);                  //加解密类型
        jsonObject.put("publicSecurity", "1234561234561234");                       //加密密钥
        jsonObject.put("privateSecurity", "1234561234561234");                      //解密密钥
        jsonObject.put("keySize", "16");                                            //密钥长度
        jsonObject.put("salt", "789789");                                           //盐值
        jsonObject.put("isComplete", BooleanEnum.NO);                               //是否完整加解密
        jsonObject.put("encryptMode", OpenApiConstans.ENCRYPT_MODE_CBC);            //加密模式
        jsonObject.put("customVersion", CustomVersionEnum.PAPH);                       //定制化版本枚举
        jsonObject.put("requestDateDirection", RequestDateDirectionEnum.RESPONSE);   //加解密入口
        jsonObject.put("isFile", BooleanEnum.NO);                                  //是否是文件
        jsonObject.put("encyAndDecyFieldKey", "infoContent");                                  //是否是文件
        jsonObject.put("dataContentKey", "infoContent");                                  //是否是文件
        jsonObject.put("signKey", "infoSign");                                  //是否是文件
        configurationValue.setSettingValue(jsonObject.toJSONString());
        List<Filter.ConfigurationValue> list = new ArrayList<Filter.ConfigurationValue>();
        list.add(configurationValue);
        return list;
    }

    /**
     * 构造请求参数
     * @return
     */
    public Context contextMorseEncrypts () {
        Context context = new Context(Maps.newHashMap());
        Context.Common common = context.getCommon();
        common.setApiIdentify("POST:/api/morse_xin_betaf4/JT001/creditApply");
        Context.ApiInfo api = new Context.ApiInfo();
        api.setAddress("/api/morse_xin_betaf4/JT001/creditApply");
        context.api(api);
        context.getRequest().setBody(getString());
        Resource<Object> ok = Resource.<Object>OK(getString());
        context.getResponse().setBody(Resource.<Object>OK(getString()));
        return context;
    }

    /**
     * 构造请求Body内容
     * @return
     */
    public String getString(){
        //测试加密时 可以使用的参数
        /*String str = "{\n" +
                "  \"requestTime\": \"20211112171405\",\n" +
                "  \"requestNo\": \"xuyy85156\",\n" +
                "  \"txCode\": \"CREDIT_APPLY\",\n" +
                "  \"infoContent\": {\n" +
                "    \"userInfo\": {\n" +
                "      \"interestRate\": \"0.0005\",\n" +
                "      \"profession\": \"工人\",\n" +
                "      \"certType\": \"10100\",\n" +
                "      \"idExpire\": \"20500809\",\n" +
                "      \"address\": \"四川省成都市双流区\",\n" +
                "      \"activateTag\": \"UN_ACTIVATED\",\n" +
                "      \"bkTel\": \"18628277822\",\n" +
                "      \"contactName\": \"李三\",\n" +
                "      \"userTel\": \"18789898223\",\n" +
                "      \"cardNo\": \"6225902784927437489\",\n" +
                "      \"contactTel\": \"18678737482\",\n" +
                "      \"applyAmount\": \"2000000\",\n" +
                "      \"certNo\": \"230102195003020861\",\n" +
                "      \"areaCode\": \"510115\",\n" +
                "      \"contactRelation\": \"父母\",\n" +
                "      \"pin\": \"榛勫崥\",\n" +
                "      \"bankNo\": \"ICBC\",\n" +
                "      \"shopPhone\": \"18628217872\",\n" +
                "      \"username\": \"张某8\"\n" +
                "    },\n" +
                "    \"riskInfo\": {\n" +
                "      \"multiData\": {\n" +
                "        \"queryCount60\": \"10\",\n" +
                "        \"queryCount7\": \"10\",\n" +
                "        \"queryCount30\": \"9\",\n" +
                "        \"queryCount180\": \"12\",\n" +
                "        \"queryCount\": \"22\",\n" +
                "        \"queryCount14\": \"16\",\n" +
                "        \"queryCount90\": \"11\"\n" +
                "      },\n" +
                "      \"creditData\": {\n" +
                "        \"btProperty\": \"90\",\n" +
                "        \"btLevel\": \"80\",\n" +
                "        \"btIdentity\": \"80\",\n" +
                "        \"btCharacteristic\": \"90\",\n" +
                "        \"btScore\": \"60\",\n" +
                "        \"btRelationshipNetwork\": \"90\",\n" +
                "        \"btPerformance\": \"90\"\n" +
                "      },\n" +
                "      \"telData\": {\n" +
                "        \"telCredibility\": \"2\",\n" +
                "        \"telUsedTime\": \"2\",\n" +
                "        \"telUsedExist\": \"1\"\n" +
                "      },\n" +
                "      \"riskData\": {\n" +
                "        \"fraudScore\": \"0.9\",\n" +
                "        \"creditUsageAmount180\": \"3\",\n" +
                "        \"addressStability\": \"2\",\n" +
                "        \"creditUsageCount180\": \"3\",\n" +
                "        \"careerForecast\": \"80\",\n" +
                "        \"carLevel\": \"9\",\n" +
                "        \"onlineAmountMax\": \"3\",\n" +
                "        \"accountUsageTimeLv\": \"5\",\n" +
                "        \"creditUsageTimeLv\": \"4\",\n" +
                "        \"incomeLevel\": \"3\",\n" +
                "        \"installmentAmount180\": \"3\",\n" +
                "        \"onlineAmountLv\": \"4\",\n" +
                "        \"houseLevel\": \"80\",\n" +
                "        \"mobileStability\": \"2\",\n" +
                "        \"installmentCount180\": \"3\"\n" +
                "      },\n" +
                "      \"addressData\": {\n" +
                "        \"addressUsedExist\": \"1\",\n" +
                "        \"addressCredibility\": \"2\",\n" +
                "        \"addressUsedTime\": \"2\"\n" +
                "      }\n" +
                "    },\n" +
                "    \"creditMode\": \"01\",\n" +
                "    \"applyNo\": \"273137918\",\n" +
                "    \"applyTime\": \"20211112171405\",\n" +
                "    \"businessType\": \"JT\"\n" +
                "  },\n" +
                "  \"version\": \"1.0\",\n" +
                "  \"channelCode\": \"JT\"\n" +
                "}";
*/
        //测试解密时 可以使用的参数
        /*
        String str = "{\n" +
                "    \"requestTime\": \"20220318173651\",\n" +
                "    \"infoSign\": \"c9cd47c29a2b9291509a56fc5d5260b6\",\n" +
                "    \"infoContent\": \"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\\r\\nSHv6iYZisqpF8litigRdwcNt2kpGykQ+2NQ+dWw=\",\n" +
                "    \"requestNo\": 50947,\n" +
                "    \"txCode\": \"CREDIT_APPLY\",\n" +
                "    \"version\": \"1.0\",\n" +
                "    \"channelCode\": \"JD_JT\"\n" +
                "}";
        */
        String str = "{\n" + "    \"companyId\": \"620\",\n" + "    \"requestData\": {\n" + "        \"channelCustomerCode\": \"PCID0260000022201181018000002120\",\n" + "        \"lendInfo\": {\n" + "            \"bankName\": \"黑龙江佳木斯郊区合作社\",\n" + "            \"bankUnionCode\": \"HLJNX\",\n" + "            \"baseRate\": 0.038,\n" + "            \"baseRateType\": \"LPR\"\n" + "        }\n" + "    },\n" + "    \"requestNo\": \"ef6cfe94-ce54-4b80-8d53-c62bba42abdd\",\n" + "    \"requestTime\": \"20220302210459\",\n" + "    \"systemCode\": \"LOAN\",\n" + "    \"tenantId\": \"zg_bank\",\n" + "    \"version\": \"1.0\"\n" + "}";
        return str;
    }

    @Test
    public void run (){
        log.debug("开始进行测试加解密功能！！！");
        Context context = contextMorseEncrypts();
        invoker().action(context, (r) -> log.error("result: {}", r.getMessage()));
        log.debug("测试加解密功能，处理完成！！！");
    }
}
